Descente du gradient + TD3 ************************** Nous avons vu que l'apprentissage requiert la minimisation d'une fonction d'erreur de :math:`\mathbb{R}^n\rightarrow \mathbb{R}`. Pour cela, une méthode très répandue existe : la méthode du gradient. Cette dernière permet itérativement de diminuer la valeur de l’erreur jusqu'à converger vers un minimum local. Dans ce chapitre, nous introduisons son principe, tout d'abord en traitant une fonction de :math:`\mathbb{R}\rightarrow \mathbb{R}`, puis ensuite une fonction de :math:`\mathbb{R}^2\rightarrow \mathbb{R}` pour terminer en généralisant la méthode aux fonctions de :math:`\mathbb{R}^n\rightarrow \mathbb{R}`. Pour une fonction de :math:`\mathbb{R}\rightarrow \mathbb{R}` ============================================================= Si nous traitons une fonction de :math:`\mathbb{R}\rightarrow \mathbb{R}`, dans ce cas particulier, la notion de gradient correspond à la notion de dérivée. Rappelons la formule d’approximation d’une fonction : .. math:: g(a+h) = g(a) + h \cdot g’(a) + \epsilon(h) ~ ~ ~ \mbox{ avec } ~ ~ ~ \lim_{h\rightarrow 0} \epsilon(h) = 0 Ce qui signifie qu’autour de la valeur :math:`a`, pour une valeur de :math:`h` « petite », la fonction :math:`g` se comporte comme une droite de pente :math:`g’(a)` : .. image:: gradrr.png :align: center :scale: 80% Considérons un processus itératif. Si l'on veut diminuer la valeur courante : :math:`g(a_i)`, il faut faire varier :math:`a_i` dans le sens opposé au signe de :math:`g’(a_i)`. En effet, si la dérivée :math:`g'(a_i)` est négative, la fonction :math:`g` est décroissante au voisinage de :math:`a_i`. Par conséquent, lorsque :math:`g'(a_i)<0`, il faut augmenter la valeur de :math:`a_i` : :math:`a_{i+1}>a_i`. De cette façon, en se déplaçant vers la droite, pour une variation suffisamment petite dénommée :math:`pas`, la valeur de :math:`g` diminue. On en déduit la formule de principe de la méthode du gradient : .. math:: a_{i+1} = a_i - pas \cdot g’(a_i) Nous utilisons cette approche pour mettre en place l’algorithme de descente du gradient : .. code-block:: Function GradientDescent(g,a) : pas = 0.01 tant que du temps est disponible : grad = g’(a) # dans notre exemple, la dérivée donne le gradient a = a – pas * grad # le signe – fait progresser dans la direction opposée au signe de grad .. note:: La méthode de descente du gradient ne garantit pas que la valeur de la fonction diminue à chaque itération. Par exemple, lorsque nous sommes proches d’un minimum, suivant la valeur du *pas*, on peut « sauter » par-dessus ce minimum pour atteindre finalement une valeur courante plus importante. .. warning:: Dans la suite, une notation avec indice du type :math:`x_i` désigne la valeur à l'itération :math:`i`. Ainsi, avec :math:`f(x)=3x^2+2`, si :math:`x_i=5`, nous pouvons évaluer la valeur de la fonction :math:`f'(x_i)` égale à :math:`30`. Exercice -------- Nous minimisions l’erreur totale d'une base contenant un unique échantillon :math:`x` ceci en utilisant un seul paramètre interne :math:`a` . Nous supposons que l'erreur totale est donnée par la fonction :math:`E(x,a) = a² + a\cdot x + 1`. .. quiz:: gradRR :title: Méthode du gradient .. csv-table:: :delim: ! Donnée en entrée ! :math:`{x} = 3` Itération courante ! :math:`{a_i} = 5` Combien vaut :math:`E(3,{a_i})` ? ! :quiz:`{"type":"FB","answer":"41"}` Combien vaut :math:`\frac{\partial E}{\partial a}(3,{a_i})` ? ! :quiz:`{"type":"FB","answer":"13"}` Pour minimiser l'erreur, augmentons-nous la valeur de :math:`{a_i}` ? ! :quiz:`{"type":"TF","answer":"F"}` Pour un pas de :math:`\frac{1}{13}`, donnez la nouvelle valeur de :math:`{a_{i+1}}` ! :quiz:`{"type":"FB","answer":"4"}` Calculez :math:`E(3, a_{i+1})` : ! :quiz:`{"type":"FB","answer":"29"}` L'erreur a-t-elle diminué ? ! :quiz:`{"type":"TF","answer":"T"}` Pour une fonction de :math:`\mathbb{R}^2\rightarrow \mathbb{R}` =============================================================== Pour minimiser une telle fonction, nous utilisons la notion de dérivée partielle qui étend la notion de dérivée d’une fonction de :math:`\mathbb{R}\rightarrow \mathbb{R}` au cas général d'une fonction de :math:`\mathbb{R}^n\rightarrow \mathbb{R}`. Prenons l’exemple d’une fonction à deux variables :math:`g(x,y)\rightarrow \mathbb{R}`. En ajoutant un paramètre de perturbation :math:`h`, nous obtenons des formules d'approximation similaires au cas précédent : .. math:: g(x+h,y) = g(x,y) + h \cdot \frac{\partial g}{\partial x} (x,y) + \epsilon(h) ~ ~ ~ \mbox{ avec } ~ ~ ~ \lim_{h\rightarrow 0} \epsilon(h) = 0 et .. math:: g(x,y+h) = g(x,y) +h \cdot \frac{\partial g}{\partial y} (x,y) + \epsilon(h) ~ ~ ~ \mbox{ avec } ~ ~ ~ \lim_{h\rightarrow 0} \epsilon(h) = 0 Comment s’interprètent les deux dérivées partielles ? Si nous faisons uniquement évoluer la valeur de :math:`x`, nous obtenons comme dans le cas 1D une droite tangente au point courant :math:`P`. De la même manière, si nous faisons évoluer :math:`y`, nous obtenons une autre droite tangente en ce point. En combinant ces deux directions tangentes, nous obtenons un plan tangent qui approche le comportement de la fonction :math:`g` autours du point :math:`P` : .. image:: cas2D.png :align: center :scale: 80% Nous utilisons la notation :math:`\nabla g` pour désigner le **gradient** de la fonction :math:`g`. Ce vecteur correspond aux dérivées partielles de la fonction :math:`g` : .. math:: \nabla g(x_i,y_i) = \begin{bmatrix} \frac{\partial g}{\partial x}(x_i,y_i) \\ \frac{\partial g}{\partial y}(x_i,y_i) \end{bmatrix} En utilisant des vecteurs, on peut regrouper les deux formules d'approximation précédentes en une seule. Ainsi, en prenant :math:`h=[h_0, h_1]`, :math:`X = [x, y]` deux vecteurs colonnes, on peut écrire : .. math:: g(X+h)=g(X) + h^\top \cdot \nabla g(X) +\epsilon(h) Pour minimiser la valeur de :math:`g`, on choisit :math:`h = -\gamma \cdot \nabla g(X)` avec :math:`\gamma` un réel positif suffisamment petit. En effet, ce choix implique : .. math:: g(X+h) \thicksim g(X) -\gamma [\nabla g(X)^\top \cdot \nabla g(X)] Dans cette expression, la partie droite entre crochets correspond à un produit scalaire entre deux vecteurs identiques, ce qui donne comme résultat un nombre positif. La valeur de :math:`\gamma` étant positive, l'expression à droite du signe - correspond ainsi à une valeur positive. En conclusion, la valeur de la fonction :math:`g` va diminuer pour une valeur de :math:`\gamma` suffisament petite. Le cas général ============== Nous étudions maintenant le cas général avec une fonction :math:`g` de :math:`\mathbb{R}^n\rightarrow \mathbb{R}`. Avec :math:`X` et :math:`h` désignant deux vecteurs de :math:`\mathbb{R}^n`, nous avons : .. math:: g(X+h) = g(X) + h^\top \cdot \nabla g(X) + \epsilon(h) Comme dans le cas précédent, il suffit de prendre :math:`h=pas.\nabla g(X)` avec :math:`pas>0` suffisamment petit pour garantir que nous réduisons la valeur courante de la fonction. Ainsi, en appliquant cette formule itérativement, nous construisons l'algorithme de descente du gradient : .. code-block:: Function GradientDescent(g,X) : pas = 0.01 # valeur du pas tant que du temps est disponible : grad = ▽g(X) # calcule les valeurs du gradient ▽g en X X = X - pas . grad # le signe – fait progresser dans la direction opposée au gradient .. note:: Pour une fonction de :math:`g` de :math:`\mathbb{R}^n\rightarrow \mathbb{R}`, le gradient :math:`\nabla g` est un vecteur de taille :math:`n` égale à la taille du vecteur :math:`X`. En effet, le gradient est un vecteur avec :math:`n` composantes correspondant aux :math:`n` dérivées partielles de :math:`g`. Par conséquent, on peut effectuer le calcul :math:`X - pas.\nabla g(X)` car :math:`X` et :math:`\nabla g(X)` sont deux vecteurs de même dimension. .. note:: Le paramètre :math:`pas` est un réel positif, ainsi le signe . dans l'expression :math:`pas.\nabla g(X)` désigne la multiplication entre un réel et un vecteur. Exercice -------- Supposons que l’erreur totale s’écrive sous la forme : :math:`E(x,a,b) = a^2 + b\cdot x + 1` avec * :math:`x` : donnée en entrée (constante). * :math:`a,b` : deux paramètres d'apprentissage. .. quiz:: gradRR2 :title: Méthode du gradient .. csv-table:: :delim: ! Donnée en entrée ! :math:`{x} = 6` Valeur à l’itération courante ! :math:`a_i = 3`, :math:`b_i = 2` Combien vaut :math:`E(6, {a_i}, {b_i})` ? ! :quiz:`{"type":"FB","answer":"22"}` Donnez les valeurs de :math:`\nabla E({a_i}, {b_i})` ! :quiz:`{"type":"FB","answer":"6"}` :quiz:`{"type":"FB","answer":"6"}` Pour un pas de :math:`\frac{1}{6}`, donnez les valeurs de :math:`a_{i+1}` et :math:`b_{i+1}` ! :quiz:`{"type":"FB","answer":"2"}` :quiz:`{"type":"FB","answer":"1"}` Calculez :math:`E({6}, a_{i+1}, b_{i+1} )` ? ! :quiz:`{"type":"FB","answer":"11"}` L'erreur a-t-elle diminué ? ! :quiz:`{"type":"TF","answer":"T"}` TD 3 ==== `Le source du Notebook `_ Vous devez effectuer ce TD et le faire valider à votre responsable de salle.